package Reeks5.VanRansbeeck.Kevin.Model;

import Reeks5.VanRansbeeck.Kevin.Model.States.Player.PlayerStateContext;
import java.util.List;
import java.util.Observable;

/* 
 * Abstractie van "een" speler voor meerdere mogelijke (kaart)spellen 
 */

abstract public class Speler extends Observable {
    protected List<Kaart> holekaarten; // kaarten die speler zelf vastheeft
    protected String naam;
    protected int saldo;
    protected Spel spel;

    
    protected PlayerStateContext stateContext; // checked-raised-call-fold
    
    protected int[] histogramTypes;
    protected int[] histogramWaarden;
    
    public Speler(Spel spel) {
        this("Anoniem", spel);
    }
    public Speler(String naam, Spel spel) {
        this.setNaam(naam);
        this.setSpel(spel);
        this.setSaldo(1000);
        this.setStateContext(new PlayerStateContext(spel.getSpelContext()));
        this.histogramTypes = new int[4];       // array van de 4 types (schoppen/...)
        this.histogramWaarden = new int[13];    // array van de 13 kaartwaardes
        this.resetHistograms();
    }

    public String getNaam() {
        return naam;
    }

    private void setNaam(String naam) {
        this.naam = naam;
    }
    
    public List<Kaart>getHolekaarten() {
        return this.holekaarten;
    }

    public int getSaldo() {
        return saldo;
    }

    private void setSaldo(int saldo) {
        this.saldo = saldo;
    }
    
    public void updateSaldo(int winst) {
        this.setSaldo(this.getSaldo() + winst);
        this.setChanged();
        this.notifyObservers();
    }

    public Spel getSpel() {
        return spel;
    }

    private void setSpel(Spel spel) {
        this.spel = spel;
    }

    public PlayerStateContext getStateContext() {
        return stateContext;
    }

    private void setStateContext(PlayerStateContext stateContext) {
        this.stateContext = stateContext;
    }
    
    
    protected void vulHistogram() {
        this.resetHistograms();
        for (Kaart kaart : this.getHolekaarten()) {
            // vul histogramTypes
            this.histogramTypes[kaart.getType().ordinal()]++;
            // vul histogramWaarden
            this.histogramWaarden[kaart.getWaarde().ordinal()]++;
        }
        for (Kaart kaart : this.getSpel().getTafel()) {
            // vul histogramTypes
            this.histogramTypes[kaart.getType().ordinal()]++;
            // vul histogramWaarden
            this.histogramWaarden[kaart.getWaarde().ordinal()]++;
        }
    }
    
    public int[] getHistogramTypes() {
        this.vulHistogram();
        return this.histogramTypes;
    }
    
    public int[] getHistogramWaarden() {
        this.vulHistogram();
        return this.histogramWaarden;
    }

    private void resetHistograms() {
        for(int i = 0; i < 4; i++) {
            this.histogramTypes[i] = 0;
        }
        for(int i = 0; i < 13; i++) {
            this.histogramWaarden[i] = 0;
        }
    }
    
    public Kaart drawKaart() {
        try {
            Kaart k = spel.getDeck().neemRandomKaart();
            this.holekaarten.add(k);
            if(this.holekaarten.size() == 2) { // die 2 moet abstract!
                this.setChanged();
            }
            this.notifyObservers("Speler"); //System.out.println(this.countObservers() + "OBSERVERS NOTIFIED"); 
            return k;
        } catch (ArrayIndexOutOfBoundsException aob) {
            System.out.println("One card too many drawn!");
            aob.printStackTrace();
            System.out.println("______SPELER_____\n" + this);
            System.out.println("_______DECK______\n" + getSpel().getDeck());
            return null;
        } catch (Exception e) {
            System.out.println(e);
            return null;
        }
    }
    
    public void printHistogram() {
        System.out.println("Histogram " + this.getNaam() + "\n");
        for(int i = 0; i < this.getHistogramTypes().length; i++) {
            System.out.println(Type.values()[i] + " : " + this.getHistogramTypes()[i]);
        }
        System.out.println("------");
        for(int i = 0; i < this.getHistogramWaarden().length; i++) {
            System.out.println(Waarde.values()[i] + " : " + this.getHistogramWaarden()[i]);
        }
    }
    
    @Override
    public String toString() {
        String ret = "Speler: " + this.getNaam() + "\n";
        if(this.getHolekaarten().size() > 0) {
            for(Kaart k : this.getHolekaarten()) {
                ret += k + "\n";
            }
        }
        ret += "Status: " + this.getStateContext().getStatus().getStatus() + "\n";
        return ret;
    }
    
    public void fold() {
        stateContext.fold();
        this.setChanged();
        this.notifyObservers(this);
    }
    
    public void resetState() {
        stateContext.reset();
        this.setChanged();
        this.notifyObservers();
    }
    
    public abstract void call(int value);
    /*
    public abstract void raise(int value);
    public abstract void bet(int value);
    public abstract void allin(int value);
    public abstract void check();
     */
}
